
package commonInfrastructure.accountManagement.managedbean;

import commonInfrastructure.accountManagement.entity.EmployeeEntity;
import commonInfrastructure.accountManagement.entity.RoleEntity;
import commonInfrastructure.accountManagement.entity.SalesmanEntity;
import commonInfrastructure.accountManagement.entity.WarehousePersonnelEntity;
import commonInfrastructure.accountManagement.session.EmailSessionBean;
import commonInfrastructure.accountManagement.session.EmployeeSessionBean;
import commonInfrastructure.accountManagement.session.PasswordHashSessionBean;
import commonInfrastructure.accountManagement.session.RoleSessionBean;
import commonInfrastructure.accountManagement.session.SalesmanSessionBean;
import commonInfrastructure.accountManagement.session.WarehousePersonnelSessionBean;
import java.io.IOException;
import java.io.Serializable;
import javax.ejb.EJB;
import javax.faces.application.FacesMessage;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.ViewScoped;
import javax.faces.context.FacesContext;
import javax.faces.event.ActionEvent;
import java.util.ArrayList;
import java.util.List;
import java.util.UUID;


@ManagedBean
@ViewScoped
public final class AddEmployeeManagedBean implements Serializable {

    @EJB
    private EmployeeSessionBean employeeManager;
    @EJB
    private RoleSessionBean roleManager;
    @EJB
    private PasswordHashSessionBean passwordHashSessionBean;
    @EJB
    private SalesmanSessionBean salesmanManager;
    @EJB
    private WarehousePersonnelSessionBean warehouseManager;
     
    @EJB
    private EmailSessionBean emailSessionBean;
    private EmployeeEntity employee;
    private String stringRoles;
    private List<RoleEntity> allRoles;
    private String[] names;
    private String[] selected;
    private List<String> selectedRoles;
    private boolean show;
    private SalesmanEntity salesman;
    private WarehousePersonnelEntity warehouseman;
    private String warehouseLevel;
    private String dl;
    private String al;

    

    public AddEmployeeManagedBean() {
        employee = new EmployeeEntity();
        salesman = new SalesmanEntity();
        warehouseman = new WarehousePersonnelEntity();
        selectedRoles = new ArrayList<String>();
        
    
    }

    public void saveNewEmployee(ActionEvent event) throws IOException {
        String initialPwd="";
        if (employeeManager.isExist(employee) ==true ) //exist already
        {
            System.out.println("User Name conflict");
            FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_INFO, "User Name Already Exists", ""));
            return;
        } else { //doesn't exist
            
            String uuid = UUID.randomUUID().toString();
            String[] sArray = uuid.split("-");
              initialPwd=sArray[0];
            employee.setPassword(initialPwd);
            employee.setPassword(passwordHashSessionBean.hashPassword(employee.getUserName()+employee.getPassword()));
            }  
         
        if(employee.getDepartment().equals("Sales Department")){//for salesman
           
            salesman.setUserName(employee.getUserName());
            salesman.setName(employee.getName());
            salesman.setDOB(employee.getDOB());
            salesman.setDepartment(employee.getDepartment());
            salesman.setRoles(employee.getRoles());
            salesman.setContactNumber(employee.getContactNumber());
            setLevel();
            salesman.setPassword(employee.getPassword());
            salesman.setPersonalEmail(employee.getPersonalEmail());
            salesman.setSecurityQuestion(employee.getSecurityQuestion());
            salesman.setAns(employee.getAns());
            try {
                pushToRoles();
                salesmanManager.addSalesman(salesman);
            } catch (Exception e) {
                FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_INFO, "Error occurs when adding new salesman", ""));
                salesman=new SalesmanEntity();
                return;
            }
            FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_INFO, "New Salesman saved.", ""));
            emailSessionBean.emailInitialPassward(salesman.getPersonalEmail(), initialPwd); //send email
            
            salesman=new SalesmanEntity();
            setShow(true);
        }
        else if(employee.getDepartment().equals("Warehouse Department")){//for warehouseman
           
            warehouseman.setUserName(employee.getUserName());
            warehouseman.setName(employee.getName());
            warehouseman.setDOB(employee.getDOB());
            warehouseman.setDepartment(employee.getDepartment());
            warehouseman.setRoles(employee.getRoles());
            warehouseman.setContactNumber(employee.getContactNumber());
            warehouseman.setWarehouseLevel(warehouseLevel);
            warehouseman.setPassword(employee.getPassword());
            warehouseman.setPersonalEmail(employee.getPersonalEmail());
            warehouseman.setSecurityQuestion(employee.getSecurityQuestion());
            warehouseman.setAns(employee.getAns());
            try {
                pushToRoles();
                warehouseManager.addWarehousePersonnel(warehouseman);
            } catch (Exception e) {
                FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_INFO, "Error occurs when adding new Warehouse Personnel", ""));
                warehouseman=new WarehousePersonnelEntity();
                return;
            }
            FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_INFO, "New Warehouse Personnel saved.", ""));
            emailSessionBean.emailInitialPassward(warehouseman.getPersonalEmail(), initialPwd); //send email
            
            warehouseman=new WarehousePersonnelEntity();
            setShow(true);
        }
        else { //others
           try{
               pushToRoles();
               employeeManager.addEmployee(employee);
           }catch (Exception e) {
               FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_INFO, "Error occurs when adding new employee", ""));
                return;
           }
            FacesContext.getCurrentInstance().addMessage(null, new FacesMessage(FacesMessage.SEVERITY_INFO, "New Employee saved.", ""));
            emailSessionBean.emailInitialPassward(employee.getPersonalEmail(), initialPwd); //send email
            
            employee=new EmployeeEntity();
            setShow(true);
        }
    }

    public void oneMore(ActionEvent event) throws IOException {
        FacesContext.getCurrentInstance().getExternalContext().redirect("AddEmployee.xhtml");
    }

    public EmployeeEntity getEmployee() {
        return employee;
    }

    public void setEmployee(EmployeeEntity employee) {
        this.employee = employee;
    }

  
    public String getStringRoles() {
        return stringRoles;
    }

    public void setStringRoles(String stringRoles) {
        this.stringRoles = stringRoles;
    }

  
    public List<RoleEntity> getAllRoles() {
        return allRoles;
    }

    public void setAllRoles(List<RoleEntity> allRoles) {
        this.setAllRoles(allRoles);
    }

    public EmployeeSessionBean getEmployeeManager() {
        return employeeManager;
    }

    public void setEmployeeManager(EmployeeSessionBean employeeManager) {
        this.employeeManager = employeeManager;
    }

    public RoleSessionBean getRoleManager() {
        return roleManager;
    }

    public void setRoleManager(RoleSessionBean roleManager) {
        this.roleManager = roleManager;
    }

    public void retrieveNames(List<RoleEntity> roles) {
        int i = 0;
        while (roles.get(i) != null) {
            getNames()[i] = roles.get(i).getRoleName();
            i++;
        }
    }

    public String[] getNames() {
        return names;
    }

   
    public void setNames(String[] names) {
        this.names = names;
    }

  
    public String[] getSelected() {
        return selected;
    }

 
    public void setSelected(String[] selected) {
        this.selected = selected;
    }

    public List<String> getSelectedRoles() {
        return selectedRoles;
    }

    public void setSelectedRoles(List<String> selectedRoles) {
        this.selectedRoles = selectedRoles;
    }

    public void pushToRoles() {
        int i = 0;
        Long id;
        id = Long.valueOf(selectedRoles.get(i));
        employee.getRoles().add(roleManager.getRole(id));
        System.out.println(selectedRoles.get(i));

        while (i < (selectedRoles.size() - 1)) {
            i++;
            id = Long.valueOf(selectedRoles.get(i));
            employee.getRoles().add(roleManager.getRole(id));
            System.out.println(selectedRoles.get(i));
        }

    }

    public boolean isShow() {
        return show;
    }

    public void setShow(boolean show) {
        this.show = show;
    }

    public boolean isSales() {
        return ("Sales Department".equals(employee.getDepartment()));
    }
    
    public boolean isWarehouse(){
        return ("Warehouse Department".equals(employee.getDepartment()));
    }

    public SalesmanEntity getSalesman() {
        return salesman;
    }

    public void setSalesman(SalesmanEntity salesman) {
        this.salesman = salesman;
    }

    public String getDl() {
        return dl;
    }

    public void setDl(String dl) {
        this.dl = dl;
    }


    public String getAl() {
        return al;
    }

    public void setAl(String al) {
        this.al = al;
    }

    public void setLevel() {
        int lv = Integer.valueOf(salesman.getSalesManLevel());
        switch (lv) {
            case 1:
                salesman.setAmountLimit(50000);
                salesman.setDiscountLimit(0.95);
                break;
            case 2:
                salesman.setAmountLimit(80000);
                salesman.setDiscountLimit(0.93);
                break;
            case 3:
                salesman.setAmountLimit(100000);
                salesman.setDiscountLimit(0.92);
                break;
            case 4:
                salesman.setAmountLimit(999999999);
                salesman.setDiscountLimit(0.90);
                break;
        }
    }

    /**
     * @return the warehouseLevel
     */
    public String getWarehouseLevel() {
        return warehouseLevel;
    }

    /**
     * @param warehouseLevel the warehouseLevel to set
     */
    public void setWarehouseLevel(String warehouseLevel) {
        this.warehouseLevel = warehouseLevel;
    }
 
}
